package com.stars.module.role.service.impl;

import com.alibaba.fastjson2.JSONArray;
import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.stars.base.constants.CommonNumberConstants;
import com.stars.base.entity.CommonDTO;
import com.stars.base.entity.Result;
import com.stars.base.entity.TreeNode;
import com.stars.module.grant.service.StarGrantService;
import com.stars.module.role.entity.StarRole;
import com.stars.module.role.mapper.StarRoleMapper;
import com.stars.module.role.service.StarRoleService;
import com.stars.util.common.DevelopKit;
import com.stars.util.tree.TreeNodeUtil;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import java.util.ArrayList;
import java.util.List;

/**
 * @author : Rocks
 * @version : 1.0
 * @date : 2022/11/25 15:28
 * @description : 角色服务实现类
 */
@Service
public class StarRoleServiceImpl implements StarRoleService {

    private final StarRoleMapper roleMapper;
    private final StarGrantService grantService;

    public StarRoleServiceImpl(StarRoleMapper roleMapper, StarGrantService grantService) {
        this.roleMapper = roleMapper;
        this.grantService = grantService;
    }

    @Override
    public JSONArray loadTree() {

        LambdaQueryWrapper<StarRole> query = new LambdaQueryWrapper<>();

        query.orderByAsc(StarRole::getShowOrder);

        JSONArray array = new JSONArray();

        List<StarRole> roleList = roleMapper.selectList(query);

        List<TreeNode> treeNodes = new ArrayList<>();

        for(StarRole role : roleList) {
            TreeNode node = new TreeNode();

            node.setValue(role.getId());
            node.setLabel(role.getRoleName());
            node.setpId(role.getFid());

            JSONObject attr = new JSONObject();
            attr.put("type",role.getDirectory());

            node.setAttr(attr);

            treeNodes.add(node);
        }

        TreeNode root = new TreeNode(CommonNumberConstants.ZERO_STR,"角色管理",CommonNumberConstants.MINUS_ONE_STR);

        array.add(TreeNodeUtil.merge(root,treeNodes).toJSON());

        return array;
    }

    @Override
    public JSONObject loadRoleListByFid(CommonDTO dto) {

        Page<StarRole> page = Page.of(dto.getCurrent(),dto.getPageSize());

        LambdaQueryWrapper<StarRole> query = new LambdaQueryWrapper<>();

        query.eq(StarRole::getFid,dto.getFid()).like(StarRole::getRoleName,dto.getSearch());
        query.orderByAsc(StarRole::getShowOrder);

        Page<StarRole> starRolePage = roleMapper.selectPage(page, query);

        JSONObject result = new JSONObject();

        result.put("list",starRolePage.getRecords());
        result.put("total",starRolePage.getTotal());

        return result;
    }

    @Override
    public Result checkRoleTypeChange(String roleId, String type) {

        if (CommonNumberConstants.ZERO_STR.equals(type)) {
            // 由文件夹变更为角色，校验文件夹下是否有有效的角色，如果有则不允许变更
            LambdaQueryWrapper<StarRole> query = new LambdaQueryWrapper<>();

            query.eq(StarRole::getFid,roleId);

            if(roleMapper.exists(query)) {
                return Result.error("当前文件夹存在有效子级，请删除子级后重试！");
            }
        } else {
            // 角色变更为文件夹，校验角色是否绑定权限和人员，如果有则不允许变更
            if(grantService.checkRoleGrant(roleId)) {
                return Result.error("当前角色有授权人员，请解除授权后重试");
            }

        }
        return Result.success();
    }

    @Override
    public boolean saveOrUpdateRole(StarRole role) {

        String roleId = role.getId();

        if(StringUtils.hasLength(roleId)){
            return roleMapper.updateById(role) > 0;
        }
        role.setId(DevelopKit.generateUUID());
        DevelopKit.setBaseInfo(role);
        return roleMapper.insert(role) > 0;
    }

    @Override
    public Result removeRole(String roleId) {

        LambdaQueryWrapper<StarRole> query = new LambdaQueryWrapper<>();

        query.eq(StarRole::getFid,roleId);

        if(roleMapper.exists(query)) {
            return Result.error("当前文件夹存在有效子级，请删除子级后重试！");
        }

        return Result.result(roleMapper.deleteById(roleId) > 0,null,"删除失败！");
    }

    @Override
    public int getMaxIndex(String fid) {

        Integer index = roleMapper.getMaxIndex(fid);

        if(index == null){
            return 0;
        }

        return index;
    }

    @Override
    public StarRole loadRoleById(String id) {
        return roleMapper.selectById(id);
    }

    @Override
    public String loadUserRoles(String userId) {
        return grantService.loadUserRoles(userId);
    }
}
